import { useEffect, useRef, useState } from 'react';

export default function Page() {
  return (
    <div
      style={{ width: '30%', background: '#ddd', fontSize: 18, lineHeight: 1 }}
    >
      <Text
        maxLine={1}
        lastWordCount={5}
        text={'<d1d11111111111111d111111111111111111111111111d'}
      />
    </div>
  );
}

function Text(props: any) {
  const { text, maxLine = 1, lastWordCount = 0, tail = '...' } = props;
  const [html, setHtml] = useState<string>('');
  const ref = useRef<any>();

  useEffect(() => {
    const resizeObserver = new ResizeObserver((entries) => {
      setText();
    });
    resizeObserver.observe(ref.current.parentNode);
    return () => {
      resizeObserver.unobserve(ref.current.parentNode);
    };
  }, []);

  function setText() {
    const parent = ref.current.parentNode;
    const width = window
      .getComputedStyle(parent, null)
      .getPropertyValue('width');
    const copy = parent.cloneNode(false);
    const current = ref.current.cloneNode(false);
    copy.appendChild(current);
    copy.style.width = width;
    // copy.style.position = 'fixed';
    // copy.style.opcity = 0;
    // copy.style.left = '99999px';
    document.body.append(copy);
    let showText = '';
    for (let i = 0; i < text.length; i++) {
      const newText = text.slice(0, i);
      showText = newText;
      current.innerText = newText;
      if (current.offsetHeight > getHeight()) {
        for (let j = newText.length; j >= 0; j--) {
          showText =
            newText.slice(0, Math.max(j - lastWordCount, 0)) +
            tail +
            newText.slice(Math.max(j - lastWordCount, 0), j);
          current.innerText = showText;
          if (current.offsetHeight === getHeight()) {
            break;
          }
        }
        break;
      }
    }
    setHtml(showText);
    // copy.remove();
  }

  function getHeight() {
    const parent = ref.current.parentNode;
    const lineHeight =
      window.getComputedStyle(parent, null).getPropertyValue('line-height') ||
      1.5715;
    const fontSize =
      parseInt(
        window.getComputedStyle(parent, null).getPropertyValue('font-size'),
      ) || 14;
    const height =
      typeof lineHeight === 'string'
        ? parseInt(lineHeight)
        : lineHeight * fontSize;
    return height * maxLine;
  }

  return (
    <div
      id={'ddd'}
      ref={ref}
      style={{ wordBreak: 'break-all', wordWrap: 'break-word' }}
    >
      {html}
    </div>
  );
}
